package com.protocols.sctp.m3ua.sccp.tcap.camel;

import java.io.Serializable;

import com.protocols.BCDNumber;
import com.protocols.OctaveInteger;
import com.protocols.ProtoOperations;
import com.protocols.ProtocolStackException;
import com.protocols.sctp.m3ua.sccp.tcap.TcapBegin;
import com.protocols.sctp.m3ua.sccp.tcap.TcapConstructor;
import com.protocols.sctp.m3ua.sccp.tcap.TcapPrimitiveUnitByteArray;
import com.protocols.sctp.m3ua.sccp.tcap.TcapPrimitiveUnitNumber;

public class CamelEventReportBCSM extends CamelInvoke implements Serializable{
	
	private TcapConstructor Parameters = new TcapConstructor(0x30);
	private TcapPrimitiveUnitNumber EventTypeBCSM = new TcapPrimitiveUnitNumber(0x80);
	private TcapConstructor EventCauseContainer = new TcapConstructor(0xa2);
	private EventSpecificInformationBCSM RouteSelectFailure = new EventSpecificInformationBCSM(0xa2);
	private EventSpecificInformationBCSM oCalledPartyBusy = new EventSpecificInformationBCSM(0xa3);
	private EventSpecificInformationBCSM oNoAnswer = new EventSpecificInformationBCSM(0xa4);
	private EventSpecificInformationBCSM oAnswer = new EventSpecificInformationBCSM(0xa5);
	private EventSpecificInformationBCSM oDisconnect = new EventSpecificInformationBCSM(0xa7);
	private EventSpecificInformationBCSM tBusy = new EventSpecificInformationBCSM(0xa8);
	private EventSpecificInformationBCSM tNoAnswer = new EventSpecificInformationBCSM(0xa9);
	private EventSpecificInformationBCSM tAnswer = new EventSpecificInformationBCSM(0xaa);
	private EventSpecificInformationBCSM tDisconnect = new EventSpecificInformationBCSM(0xac);
	
	private TcapConstructor LegIDContainer = new TcapConstructor(0xa3);
	private TcapPrimitiveUnitNumber ReceivingSideID = new TcapPrimitiveUnitNumber(0x81);
	private TcapConstructor MissCallInfoContainer = new TcapConstructor(0xa4);
	private TcapPrimitiveUnitNumber MissCallInfo = new TcapPrimitiveUnitNumber(0x80);
	private TcapPrimitiveUnitByteArray Extensions = new TcapPrimitiveUnitByteArray(0xa5);
	
	public CamelEventReportBCSM() {
		super();		
		setOpCode(24,true);	// Event Report BCSM
		super.Invoke.addElement(Parameters);
		Parameters.addElement(EventTypeBCSM);
		Parameters.addElement(EventCauseContainer);
		EventCauseContainer.addElement(RouteSelectFailure.getRootElement());
		EventCauseContainer.addElement(oCalledPartyBusy.getRootElement());
		EventCauseContainer.addElement(oNoAnswer.getRootElement());
		EventCauseContainer.addElement(oAnswer.getRootElement());
		EventCauseContainer.addElement(oDisconnect.getRootElement());
		EventCauseContainer.addElement(tBusy.getRootElement());
		EventCauseContainer.addElement(tNoAnswer.getRootElement());
		EventCauseContainer.addElement(tAnswer.getRootElement());
		EventCauseContainer.addElement(tDisconnect.getRootElement());
		EventCauseContainer.addElement(oDisconnect.getRootElement());
		
		Parameters.addElement(LegIDContainer);
		LegIDContainer.addElement(ReceivingSideID);
		Parameters.addElement(MissCallInfoContainer);
		MissCallInfoContainer.addElement(MissCallInfo);
		Parameters.addElement(Extensions);
		
	}
		
	
	
	public TcapConstructor getRootComponent(){
		return Invoke;
	}



	public long getEventTypeBCSM() {
		return EventTypeBCSM.getTagValue();
	}



	public void setEventTypeBCSM(long eventTypeBCSM) {
		EventTypeBCSM.setTagValue(eventTypeBCSM);
	}
	

	public void setLegId(int legid){
		ReceivingSideID.setTagValue(legid);
		
		
	}
	
	
	public void getLegId(){
		ReceivingSideID.getTagValue();			
		
		
	}
	
	public int getCauseLocation(){
		
		return getBCSMInformationType().getCauseLocation();
	}

	public int getCodingStandard(){
		
		return getBCSMInformationType().getCodingStandard();
	}
	
	public int getExtension1(){
		
		return getBCSMInformationType().getExtension1();
	}

	public Boolean isExtension1Available(){
		
		return getBCSMInformationType().isExtension1Available();
	}
	
	public int getCause(){
		return getBCSMInformationType().getCause();
	}

	public int getExtension2(){
		return getBCSMInformationType().getExtension2();
		
	}

	public Boolean isExtension2Available(){
		
		return getBCSMInformationType().isExtension2Available();
	}

	public void setEventSpecificInformationBCSM(int eventype,int causelocation, int codingstandard, int cause){  
		
		setEventTypeBCSM(eventype);
		getBCSMInformationType().setCause(causelocation, codingstandard, cause);
	}
	
	
	public long getMissCallInfo() {
		return MissCallInfo.getTagValue();
	}



	public void setMissCallInfo(long missCallInfo) {
		MissCallInfo.setTagValue( missCallInfo);
	}
	
	
	
	
	
	
	
	
	
	
	
	
	private EventSpecificInformationBCSM getBCSMInformationType(){
		switch ((int)getEventTypeBCSM()) {
        case 4:  return RouteSelectFailure;
        case 5:  return oCalledPartyBusy;
        case 6:  return oNoAnswer;
        case 7:  return oAnswer;
        case 9:  return oDisconnect;
        case 13:  return tBusy;
        case 14:  return tNoAnswer;
        case 15:  return tAnswer;
        case 17:  return tDisconnect;
        default: return null;
		}
		
	}
	
	
	private class EventSpecificInformationBCSM implements Serializable{
		
		private TcapConstructor EventType = new TcapConstructor(); 
		private TcapPrimitiveUnitByteArray EventCause = new TcapPrimitiveUnitByteArray(0x80);
		
		private EventSpecificInformationBCSM(int eventtype){
			EventType.setTag(eventtype);
			EventType.addElement(EventCause);
		}
		
		public int getCauseLocation(){
			
			return (EventCause.getTagValue()[0] & 0b00001111);
		}
	
		public int getCodingStandard(){
			
			return (EventCause.getTagValue()[0] & 0b01100000)>>5;
		}
		
		public int getExtension1(){
			
			if (isExtension1Available()){
				return (EventCause.getTagValue()[1] & 0xff);
			}
			return 0;
		}

		public Boolean isExtension1Available(){
			
			return ((EventCause.getTagValue()[0] & 0xff) >=80);
		}
		
		public int getCause(){
			if (isExtension1Available()){
				return (EventCause.getTagValue()[2] & 0x7f);
			}	
			return (EventCause.getTagValue()[1] & 0x7f);
		}

		public int getExtension2(){
			if (isExtension1Available() && isExtension2Available()){
				return (EventCause.getTagValue()[3] & 0xff);
			}
			else if (!isExtension1Available() && isExtension2Available()){
				return (EventCause.getTagValue()[2] & 0xff);
			}
			return 0;
			
		}

		public Boolean isExtension2Available(){
			
			if (isExtension1Available())
				return ((EventCause.getTagValue()[2] & 0xff) >=80);
			else
				return ((EventCause.getTagValue()[1] & 0xff) >=80);
		}

		public void setCause(int causelocation, int codingstandard, int cause){  
			
			EventCause.setTagValue(new byte[] {(byte)(0x80|(codingstandard<<5)|causelocation),(byte)(0x80|cause)});
		}
		
		
		
		
		
		public TcapConstructor getRootElement(){
			return EventType;
		}
		
	}



}
